#include "key_driver.h"

static void key_init(void);
static void key_task(void);
static int key_get_result(key_result_e * key_result);

key_driver_t key_driver[KEY_MAX_TYPE];

static QueueHandle_t key_driver_event_queue = NULL;

key_driver_ops_t key_driver_ops = {
	.pfinit = key_init,
	.pftask = key_task,
	.pfget_result = key_get_result,
};

static void key_init(void)
{
	key_driver_event_queue = xQueueCreate(10,sizeof(key_event_e));
}

static void key_task(void)
{
	static uint32_t key_tick = 0;
	GPIO_PinState key_status = 0;
	uint32_t system_tick = 0;
	
	key_status = HAL_GPIO_ReadPin(KEY_USER_PORT,KEY_USER_PIN);
	
	for(key_type_e key_type = KEY_USER_TYPE;key_type < KEY_MAX_TYPE;key_type++)
	{
		switch(key_driver[key_type].key_event)
		{
			case (KEY_IDLE_EVENT):
				if(key_status == GPIO_PIN_RESET)
				{
					key_driver[key_type].key_event = KEY_TRIGGER_EVENT;
					key_tick = HAL_GetTick();
				}
				break;
				
			case (KEY_TRIGGER_EVENT):
				system_tick = HAL_GetTick();
				if((key_status == GPIO_PIN_SET) && (system_tick - key_tick > 50) && (system_tick - key_tick < 3000))
				{
					key_driver[key_type].key_event = KEY_SHORT_EVENT;
					key_tick = system_tick;
				}
				else if((key_status == GPIO_PIN_RESET) && (system_tick - key_tick > 3000))
				{
					key_driver[key_type].key_event = KEY_LONG_EVENT;
					key_tick = system_tick;
				}
				else if(system_tick - key_tick > 3000)
				{
					key_driver[key_type].key_event = KEY_IDLE_EVENT;
					key_tick = system_tick;
				}
				break;
			
			case (KEY_SHORT_EVENT):
				system_tick = HAL_GetTick();
				if(key_status == GPIO_PIN_RESET && system_tick - key_tick < 100)
				{
					key_driver[key_type].key_event = KEY_DOUBLE_EVENT;
					key_tick = system_tick;
				}
				else if(system_tick - system_tick > 100)
				{
					key_driver[key_type].key_result = KEY_SHORT_PRESS;
					key_driver[key_type].key_event = KEY_IDLE_EVENT;
					xQueueSend(key_driver_event_queue,&key_driver[key_type].key_result,100);
				}
				break;
			
			case (KEY_LONG_EVENT):
				key_driver[key_type].key_result = KEY_LONG_PRESS;
				key_driver[key_type].key_event = KEY_IDLE_EVENT;
				xQueueSend(key_driver_event_queue,&key_driver[key_type].key_result,100);
				break;
			
			case (KEY_DOUBLE_EVENT):
				key_driver[key_type].key_result = KEY_DOUBLE_PRESS;
				key_driver[key_type].key_event = KEY_IDLE_EVENT;
				xQueueSend(key_driver_event_queue,&key_driver[key_type].key_result,100);
				break;
			
			default:
				break;
		}
	}
}

static int key_get_result(key_result_e * key_result)
{
	if(xQueueReceive(key_driver_event_queue,key_result,portMAX_DELAY) == pdTRUE)
		return 1;
	return 0;
}
